package com.iocup.keybastion.configuration;



import com.iocup.keybastion.annotion.HasAuthorization;
import com.iocup.keybastion.annotion.HasPermission;
import com.iocup.keybastion.annotion.HasRole;
import com.iocup.keybastion.annotion.RequiresUser;
import com.iocup.keybastion.authorize.DefaultHasAuthorizationProvider;
import com.iocup.keybastion.authorize.HasAuthorizationProvider;
import com.iocup.keybastion.authorize.decision.AuthDecision;
import com.iocup.keybastion.authorize.decision.AuthDecisionFinder;
import com.iocup.keybastion.authorize.decision.DefaultAuthDecisionFinder;
import com.iocup.keybastion.authorize.element.AuthElementProvider;
import com.iocup.keybastion.authorize.element.AuthElementService;
import com.iocup.keybastion.authorize.element.DefaultAuthElementService;
import com.iocup.keybastion.authorize.parser.*;

import lombok.Getter;

/**
 * @author xyjxust
 * @create 2022/2/23 14:25
 **/
public class AuthorizationConfigurator {

    /**
     * 是否启用权限判断
     */
    private boolean enabled = true;
    /**
     * 数据源提供者
     */
    @Getter
    private AuthElementService authElementService = new DefaultAuthElementService();
    /**
     * 权限决断查找器
     */
    @Getter
    private AuthDecisionFinder authDecisionFinder = new DefaultAuthDecisionFinder();
    /**
     * 权限注解解析器
     */
    private AuthAnnotationParser authAnnotationParser = new DefaultAuthAnnotationParser();

    /**
     * 配置文件的权限认证配置
     */
    @Getter
    private PermissionProperties permissionProperties = new PermissionProperties();

    private HasAuthorizationProvider hasAuthorizationProvider = new DefaultHasAuthorizationProvider();

    /**
     * 是否启用
     *
     * @return
     */
    public AuthorizationConfigurator disabled() {
        this.enabled = false;
        return this;
    }

    /**
     * 添加权限元素来源
     *
     * @param authElementProvider
     * @return
     */
    public AuthorizationConfigurator addAuthElementProvider(AuthElementProvider authElementProvider) {
        this.authElementService.addProvider(authElementProvider);
        return this;
    }

    /**
     * 添加权限判断器
     *
     * @param decision
     * @return
     */
    public AuthorizationConfigurator addDecision(AuthDecision decision) {
        this.authDecisionFinder.addDecision(decision);
        return this;
    }

    /**
     * 添加注解解析器
     *
     * @param authAnnoObjects
     * @return
     */
    public AuthorizationConfigurator addAnnotationParser(AuthAnnoObject...  authAnnoObjects) {
        this.authAnnotationParser.addAuthAnnoObject(authAnnoObjects);
        return this;
    }

    /**
     * 配置文件的权限配置
     * @param permissionProperties
     * @return
     */
    public AuthorizationConfigurator permissionProperties(PermissionProperties permissionProperties){
        this.permissionProperties = permissionProperties;
        return this;
    }

    /**
     * 当前登录人的权限提供器
     * @param hasAuthorizationProvider
     * @return
     */
    public AuthorizationConfigurator hasAuthorizationProvider(HasAuthorizationProvider hasAuthorizationProvider){
        this.hasAuthorizationProvider = hasAuthorizationProvider;
        return this;
    }

    public AuthAnnotationParser getAuthAnnotationParser() {
        AuthAnnotationParser  annotationParser =  authAnnotationParser == null?new DefaultAuthAnnotationParser():this.authAnnotationParser;
        annotationParser.addAuthAnnoObject(new AuthAnnoObject(RequiresUser.class,new RequiresUserElementParser()),
                new AuthAnnoObject(HasRole.class,new HasRoleElementParser()),
                new AuthAnnoObject(HasPermission.class,new HasPermissionElementParser()),
                new AuthAnnoObject( HasAuthorization.class,new HasAuthorizationElementParser()));
        return annotationParser;
    }

    public HasAuthorizationProvider getHasAuthorizationProvider() {
        return hasAuthorizationProvider==null?new DefaultHasAuthorizationProvider():this.hasAuthorizationProvider;
    }
}
